﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.Serialization;
using System.Text;
using WebChatApi.Common.Interface;

namespace WebChatApi.Common
{
    /// <summary>
    /// Class for content based template
    /// </summary>
    [DataContract]
    [KnownType(typeof(BaseObject))]
    public class Template : BaseObject
    {
        /// <summary>
        /// Enum for PlaceHolderKeywords
        /// </summary>
        [DataContract]
        public enum PlaceHolderKeywords
        {
            /// <summary>
            /// The user name
            /// </summary>
            [EnumMember]
            UserName = 0,
            /// <summary>
            /// The user key
            /// </summary>
            [EnumMember]
            UserKey,
            /// <summary>
            /// The user first name
            /// </summary>
            [EnumMember]
            UserFirstName,
            /// <summary>
            /// The user middle name
            /// </summary>
            [EnumMember]
            UserMiddleName,
            /// <summary>
            /// The user last name
            /// </summary>
            [EnumMember]
            UserLastName,
            /// <summary>
            /// The user email
            /// </summary>
            [EnumMember]
            UserEmail,
            /// <summary>
            /// The user cell phone
            /// </summary>
            [EnumMember]
            UserCellPhone,
            /// <summary>
            /// The template key
            /// </summary>
            [EnumMember]
            TemplateKey,
            /// <summary>
            /// The version stamp
            /// </summary>
            [EnumMember]
            VersionStamp
        }

        #region Properties

        /// <summary>
        /// Gets or sets the name.
        /// </summary>
        /// <value>
        /// The name.
        /// </value>
        [DataMember]
        public string Name
        {
            get;
            set;
        }

        /// <summary>
        /// Gets or sets the content.
        /// </summary>
        /// <value>
        /// The content.
        /// </value>
        [DataMember]
        public string Content
        {
            get;
            set;
        }

        /// <summary>
        /// Gets the predefined holder keywords.
        /// </summary>
        /// <value>
        /// The predefined holder keywords.
        /// </value>
        public virtual string[] PredefinedHolderKeywords
        {
            get
            {
                return Enum.GetNames(typeof(PlaceHolderKeywords));
            }
        }

        #endregion

        #region Public methods

        /// <summary>
        /// Generates the content of the filled.
        /// </summary>
        /// <param name="placeHolders">The place holders.</param>
        /// <returns></returns>
        public string GenerateFilledContent(Dictionary<string, string> placeHolders)
        {
            return GenerateContent(this.Content, placeHolders);
        }

        #endregion

        /// <summary>
        /// Gets the replace value.
        /// </summary>
        /// <param name="holderKeyword">The holder keyword.</param>
        /// <param name="template">The template.</param>
        /// <param name="userInfo">The user info.</param>
        /// <param name="versionStamp">The version stamp.</param>
        /// <returns></returns>
        public static string GetReplaceValue(string holderKeyword, Template template, IUserInfo userInfo, string versionStamp)
        {
            PlaceHolderKeywords holderKey;
            if (Enum.TryParse<PlaceHolderKeywords>(holderKeyword, out holderKey))
            {
                return GetReplaceValue(holderKey, template, userInfo, versionStamp);
            }

            return string.Empty;
        }

        /// <summary>
        /// Gets the replace value.
        /// </summary>
        /// <param name="holderKeyword">The holder keyword.</param>
        /// <param name="template">The templage.</param>
        /// <param name="userInfo">The user info.</param>
        /// <param name="versionStamp">The version stamp.</param>
        /// <returns></returns>
        public static string GetReplaceValue(PlaceHolderKeywords holderKeyword, Template template, IUserInfo userInfo, string versionStamp)
        {
            string result = string.Empty;

            if (userInfo != null && template != null)
            {
                switch (holderKeyword)
                {
                    case PlaceHolderKeywords.TemplateKey:
                        result = template.Key.ToString();
                        break;
                    case PlaceHolderKeywords.VersionStamp:
                        result = versionStamp;
                        break;
                    case PlaceHolderKeywords.UserCellPhone:
                        result = userInfo.CellPhone;
                        break;
                    case PlaceHolderKeywords.UserEmail:
                        result = userInfo.EmailAddress;
                        break;
                    case PlaceHolderKeywords.UserFirstName:
                        result = userInfo.FirstName;
                        break;
                    case PlaceHolderKeywords.UserLastName:
                        result = userInfo.LastName;
                        break;
                    case PlaceHolderKeywords.UserMiddleName:
                        result = userInfo.MiddleName;
                        break;
                    case PlaceHolderKeywords.UserKey:
                        result = userInfo.Key.ToString();
                        break;
                    case PlaceHolderKeywords.UserName:
                        result = string.Format("{0} {1} {2}",
                            userInfo.LastName.GetStringValue(),
                            userInfo.MiddleName.GetStringValue(),
                            userInfo.FirstName.GetStringValue()).Replace("  ", " ");
                        break;
                    default:
                        break;
                }
            }
            return result;
        }


        /// <summary>
        /// Generates the content.
        /// </summary>
        /// <param name="template">The template.</param>
        /// <param name="placeHolders">The place holders.</param>
        /// <returns></returns>
        public static string GenerateContent(string template, Dictionary<string, string> placeHolders)
        {
            if (!string.IsNullOrWhiteSpace(template))
            {
                foreach (var key in placeHolders.Keys)
                {
                    template = template.Replace(GeneratePlaceHolderSign(key), placeHolders[key].GetStringValue());
                }
            }

            return template;
        }

        /// <summary>
        /// Generates the place holder sign.
        /// </summary>
        /// <param name="keyword">The keyword.</param>
        /// <returns></returns>
        public static string GeneratePlaceHolderSign(string keyword)
        {
            return string.IsNullOrWhiteSpace(keyword) ? string.Empty : string.Format("[@{0}]", keyword);
        }

        /// <summary>
        /// Generates the place holder sign.
        /// </summary>
        /// <param name="keyword">The keyword.</param>
        /// <returns></returns>
        public static string GeneratePlaceHolderSign(Template.PlaceHolderKeywords keyword)
        {
            return GeneratePlaceHolderSign(keyword.ToString());
        }
    }
}
